/*
** pictor.h
**
** Pictor, Version 1.51, Copyright (c) 1992-94 SoftCircuits
** Redistributed by permission.
*/

#ifndef PICTOR_H
#define PICTOR_H

/* If using the Watcom C compiler, multiple calling conventions are used- W. Jones. */
#ifdef __WATCOMC__
	#define C_DECL __cdecl
#endif

/* constants */
#define TRUE            0x01
#define FALSE           0x00

#define COLOR_SEG       0xB800
#define MONO_SEG        0xB000
#define CGA_STATUS_PORT 0x03DA

#define BLACK           0x00
#define BLUE            0x01
#define GREEN           0x02
#define CYAN            0x03
#define RED             0x04
#define MAGENTA         0x05
#define YELLOW          0x06
#define WHITE           0x07
#define BOLD            0x08
#define BLINKING        0x10

/* keyboard constants */
#define ESCAPE_KEY      0x011B
#define TAB_KEY         0x0F09
#define SHIFTTAB_KEY    0x0F00
#define ENTER_KEY       0x1C0D
#define SPACE_BAR       0x3920
#define BACKSPACE_KEY   0x0E08
#define INSERT_KEY      0x5200
#define DELETE_KEY      0x5300
#define HOME_KEY        0x4700
#define UP_KEY          0x4800
#define PGUP_KEY        0x4900
#define PGDN_KEY        0x5100
#define LEFT_KEY        0x4B00
#define RIGHT_KEY       0x4D00
#define END_KEY         0x4F00
#define DOWN_KEY        0x5000

#define F1_KEY          0x3B00
#define F2_KEY          0x3C00
#define F3_KEY          0x3D00
#define F4_KEY          0x3E00
#define F5_KEY          0x3F00
#define F6_KEY          0x4000
#define F7_KEY          0x4100
#define F8_KEY          0x4200
#define F9_KEY          0x4300
#define F10_KEY         0x4400

#define ALT_A           0x1E00
#define ALT_B           0x3000
#define ALT_C           0x2E00
#define ALT_D           0x2000
#define ALT_E           0x1200
#define ALT_F           0x2100
#define ALT_G           0x2200
#define ALT_H           0x2300
#define ALT_I           0x1700
#define ALT_J           0x2400
#define ALT_K           0x2500
#define ALT_L           0x2600
#define ALT_M           0x3200
#define ALT_N           0x3100
#define ALT_O           0x1800
#define ALT_P           0x1900
#define ALT_Q           0x1000
#define ALT_R           0x1300
#define ALT_S           0x1F00
#define ALT_T           0x1400
#define ALT_U           0x1600
#define ALT_V           0x2F00
#define ALT_W           0x1100
#define ALT_X           0x2D00
#define ALT_Y           0x1500
#define ALT_Z           0x2C00

#define ALT_0           0x8100
#define ALT_1           0x7800
#define ALT_2           0x7900
#define ALT_3           0x7A00
#define ALT_4           0x7B00
#define ALT_5           0x7C00
#define ALT_6           0x7D00
#define ALT_7           0x7E00
#define ALT_8           0x7F00
#define ALT_9           0x8000

/* messagebox arguments */
#define MB_OK           0
#define MB_OKCANCEL     1
#define MB_RETRYCANCEL  2
#define MB_RETRYABORT   3
#define MB_YESNO        4
#define MB_YESNOCANCEL  5

/* wopen arguments */
#define WO_SHADOW       0x0001
#define WO_TEXTCURSOR   0x0002
/* #define WO_NOFRAME      0x0004 */
#define WO_STATICMEM    0x0008
#define WO_TEXTWRAP     0x0010

/* wpane arguments */
#define WP_VERTICAL     0x0001
#define WP_HORIZONTAL   0x0002

/* MAINMENU and SUBMENU  contants */
#define SUBMENU_DIVIDER {(char *)-1,(char *)-1,NULL,(void (*)(void))0}
#define END_SUBMENU     {NULL,NULL,NULL,(void (*)(void))0}
#define END_MAINMENU    {NULL,NULL,NULL,NULL}


/* data structures */
typedef struct _SUBMENU {
	char *item;
	char *description;
	char *helptopic;
	void (*function)(void);
} SUBMENU;

typedef struct _MAINMENU {
	char *item;
	char *description;
	char *helptopic;
	SUBMENU *submenu;
} MAINMENU;

typedef struct _PANESTRUCT {
	int top;
	int left;
	int height;
	int width;
	int row,column;
	int color;
} PANESTRUCT;

typedef struct _WINDOW {
	struct _WINDOW *next;
	int oldcurspos;
	int oldcurstype;
	int top;
	int left;
	int height;
	int width;
	int style;
	int color;
	int *buffer;
	int numpanes;
	int currpane;
	PANESTRUCT panes[1];
} WINDOW;

typedef struct _COLORSTRUCT {
	int normal;
	int boldnormal;
	int select;
	int boldselect;
} COLORSTRUCT;

typedef struct _VIDEOSTRUCT {
	unsigned segment;
	int snowcheck;
	int rows;
	int columns;
	int mode;
	int page;
	int colorsupport;
} VIDEOSTRUCT;

typedef struct _MEDITSTRUCT {
	char *prompt;
	char *buffer;
	int maxlen;
} MEDITSTRUCT;


extern int _PL_segment,_PL_offset;
extern int _PL_color,_PL_snowcheck;
extern int _PL_rows,_PL_columns;
extern int _PL_mode,_PL_page;
extern int _PL_colorsupport;
extern int _PL_menurow,_PL_statusrow;
extern int _PL_shadowcolor;
extern int _PL_pushedkey,_PL_escape;
extern int _PL_errorbeep;
extern int (*_PL_helpfunc)();
extern char *_PL_helpcontext;
extern WINDOW *_PL_winhead;

/* My personal data structures follow- W. Jones. */
#ifdef MOUSE_SUPPORT
extern int _PL_mousepresent;
#endif

#define _CURR_WPANE (_PL_winhead->panes[_PL_winhead->currpane])

/* macros */
#define center(_a,_b) ((((_b) - (_a)) / 2) + 1)
#define cleareol() \
	{ if(getvcol() <= _PL_columns) vrepc(' ',(_PL_columns - getvcol()) + 1); }
#define escpressed() (_PL_escape)
#define foreback(_f,_b) \
	(((_f) & 0x0F) | (((_f) & 0x10) << 3) | (((_b) & 0x07) << 4))
#define getcurscol() (getcurs() & 0xFF)
#define getcursrow() ((getcurs() >> 8) & 0xFF)
#define getvcol() (((_PL_offset / 2) % _PL_columns) + 1)
#define getvrow() (((_PL_offset / 2) / _PL_columns) + 1)
#define getwcols() (_CURR_WPANE.width - 2)
#define getwrows() (_CURR_WPANE.height - 2)
#define helpgetcontext() (_PL_helpcontext)
#define helpsetcontext(_s) (_PL_helpcontext = _s)
#define kbdpush(_x) (_PL_pushedkey = _x)
#define seterrorbeep(_x) (_PL_errorbeep = _x)
#define setdoubleframe() \
	setframe('\xCD','\xBA','\xC9','\xBB','\xC8','\xBC')
#define setsingleframe() \
	setframe('\xC4','\xB3','\xDA','\xBF','\xC0','\xD9')
#define setvpos(_r,_c) \
	(_PL_offset = (((((_r) - 1) * _PL_columns) + ((_c) - 1)) * 2))
#define snowcheckoff() (_PL_snowcheck = FALSE)
#define synccurs() setcurs(getvrow(),getvcol())
#define syncvpos() setvpos(getcursrow(),getcurscol())
#define vcolor(_c) (_PL_color = _c)

/* For Watcom C compiler, ALL Assembly routines use C-calling convention (__cdecl), unless passed into
 * atexit(), in which case Watcom calling convention (__watcall) is required. 
 * In the context of having no input parameters, __cdecl and __watcall are
 * effectively equivalent (AX return, no values to pass to stack
 * or registers), except for the fact that __watcall enforces that all
 * registers be preserved (except for those used for return values). 
 * Code to preserve registers is added as needed- W. Jones. */
 
 /* For Watcom C compiler, messagebox() is the only C-written routine using the C-calling convention.
  * It is called from the critical error handler interrupt, which itself
  * is written to pass all parameters to the stack (__cdecl) before calling
  * messagebox()- W. Jones. */

/* function prototypes */
void beep(void);
void clrstatus(void);
void cls(void);
int editbox(char *,char *,int,char *,COLORSTRUCT *);
void frame(int,int,int,int);
int getaltkey(int);
int getcurs(void);
int getcurstype(void);
int gethotkey(char *);
void getscrn(int *,int,int,int,int);
void getvconfig(VIDEOSTRUCT *);
int getwcol(void);
int getwrow(void);
void helpclose(void);
void helpopen(char *,COLORSTRUCT *,COLORSTRUCT *);
int helprun(char *);
int C_DECL hookints(COLORSTRUCT *);
void hputs(char *,int);
int hstrlen(char *);
void initstatus(int,int);
void initvideo(void);
int C_DECL installclock(int,int,int);
int kbdedit(char *,int,int,int,int,COLORSTRUCT *);
int kbdflush(void);
int kbdread(void);
int kbdready(void);
int kbdshift(void);
int listbox(char **,int,int *,char *,COLORSTRUCT *);
int C_DECL messagebox(char *,char *,int,COLORSTRUCT *);
int multiedit(MEDITSTRUCT *,int,char *,COLORSTRUCT *);
void pause(int);
char *pickfile(char *,char *,COLORSTRUCT *);
int popcurs(void);
int popstatus(void);
int prnputc(char);
int prnputs(char *);
int C_DECL prnwrite(char *,int);
int pushcurs(void);
int pushstatus(void);
void putscrn(int *,int,int,int,int);
#ifdef __WATCOMC__
	int __watcall removeclock(void);
#else
	int __cdecl removeclock(void);
#endif
int runmenu(MAINMENU *,COLORSTRUCT *,COLORSTRUCT *);
void scroll(int,int,int,int,int);
void setcurs(int,int);
void setcurstype(int);
void setframe(char,char,char,char,char,char);
int setwpane(int);
void setwpos(int,int);
void showcurs(int);
void showmenu(MAINMENU *,COLORSTRUCT *,int);
void statusbar(char *);
void tone(int,int);
#ifdef __WATCOMC__
	int __watcall unhookints(void);
#else
	int __cdecl unhookints(void);
#endif
int vgetca(void);
void vputa(int);
void vputc(char);
void vputca(int);
void vputs(char *);
void vrepa(int,int);
void vrepc(char,int);
void wclear(void);
void wcleareol(void);
void wclose(void);
void wcloseall(void);
void wcolor(int);
int wopen(int,int,int,int,int,int);
int wpane(int,int);
void wputc(char);
void wputs(char *);
void wrepa(int,int);
void wrepc(char,int);
void wsynccurs(void);
void wtitle(char *);
void xprintf(void (*)(),char *,...);

/* Wrapper functions for WATCOM's C std libraries which have no
 * __cdecl equivalent. */
#ifdef __WATCOMC__
	int WCD_atexit(void (*)());
	//WCD_sprintf(void (*)());
	
#endif

#endif
